跳到主要内容

给集群外的服务配置域名

如何使用集群内的 ClusterIssuer 给集群外的服务配置域名访问

配置公网域名

1、创建 ClusterIssuer 创建一个 ClusterIssuer 资源,用于向证书颁发机构(如Let's Encrypt)请求SSL/TLS证书。

apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
name: letsencrypt-prod
spec:
acme:
email: your-email@example.com
server: https://acme-v02.api.letsencrypt.org/directory
privateKeySecretRef:
name: letsencrypt-prod
solvers:
- http01:
ingress:
class: nginx

在这个例子中,我们使用 Let's Encrypt 的 ACME 服务器,并配置了 HTTP-01 挑战解决方案。

2、创建 DNS 记录 在 DNS 提供商处为你的服务创建一个 A 或者 CNAME 记录,指向你的集群外服务的 IP 地址或者域名。

3、创建 Ingress 资源 接下来,创建一个 Ingress 资源,用于将外部流量路由到你的服务,并使用上面创建的 ClusterIssuer 来获取 SSL/TLS 证书。

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: example-ingress
annotations:
cert-manager.io/cluster-issuer: "letsencrypt-prod"
spec:
rules:
- host: your-service.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: example-service
port:
number: 80
tls:
- hosts:
- your-service.example.com
secretName: example-tls

这个创建了一个 Ingress 资源,用于将流量路由到 example-service 服务。Cert-Manager 将使用 letsencrypt-prod ClusterIssueryour-service.example.com 域名获取一个SSL/TLS证书,并将证书存储在 example-tls 这个 Kubernetes Secret 中。

等待 Cert-Manager 获取并安装证书后,你应该能够通过 HTTPS 访问你的服务。你可以使用 kubectl 来检查证书和Ingress资源的状态。

kubectl get certificate
kubectl get ingress

确保证书状态为Ready: True,并且Ingress资源显示你的域名和正确的TLS配置。

4、现在创建一个 Endpoints 将宿主机的一个端口映射到服务的 80 端口。

apiVersion: v1
kind: Endpoints
metadata:
name: external-service
subsets:
- addresses:
- ip: <宿主机IP地址>
ports:
- port: 8080

创建 Service

apiVersion: v1
kind: Service
metadata:
name: external-service
spec:
ports:
- protocol: TCP
port: 80
targetPort: 8080

注意,Service 没有选择器(selector),所以它不会选择任何 Pod。

导出生成的证书

先导出证书

# 查看 internal-ca-issuer ClusterIssuer 的配置,找到它使用的 CA 证书存储在哪个 Secret 中。
kubectl get clusterissuer internal-ca-issuer -o yaml
# 导出 CA 证书
kubectl get secret <CA-Secret-Name> -o jsonpath="{.data['ca\.crt']}" | base64 --decode > ca.crt
# 验证 CA 证书
openssl x509 -in ca.crt -text -noout

导出域名相关证书

例如域名是 harbor-cert-secret 这里存储

# 导出域名的 TLS 证书:
kubectl get secret harbor-cert-secret -n common-namespace -o jsonpath="{.data['tls\.crt']}" | base64 --decode > tls.crt
# 导出域名的私钥:
kubectl get secret harbor-cert-secret -n common-namespace -o jsonpath="{.data['tls\.key']}" | base64 --decode > tls.key